package com.zzh.partnersys.ai.config;

import co.elastic.clients.elasticsearch.ElasticsearchClient;
import co.elastic.clients.json.jackson.JacksonJsonpMapper;
import co.elastic.clients.transport.ElasticsearchTransport;
import co.elastic.clients.transport.rest_client.RestClientTransport;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule;
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer;
import org.apache.http.HttpHost;
import org.apache.http.auth.AuthScope;
import org.apache.http.auth.UsernamePasswordCredentials;
import org.apache.http.client.CredentialsProvider;
import org.apache.http.impl.client.BasicCredentialsProvider;
import org.elasticsearch.client.RestClient;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import lombok.extern.slf4j.Slf4j;

@Configuration
@Slf4j
public class ElasticsearchConfig {
    
    @Value("${spring.elasticsearch.host:localhost}")
    private String host;

    @Value("${spring.elasticsearch.port:9200}")
    private int port;

    @Value("${spring.elasticsearch.username:elastic}")
    private String username;

    @Value("${spring.elasticsearch.password:ctRogdpvuoJNveENKsz2}")
    private String password;

    @Bean
    public RestClient restClient() {
        // 设置认证
        final CredentialsProvider credentialsProvider = new BasicCredentialsProvider();
        credentialsProvider.setCredentials(
                AuthScope.ANY,
                new UsernamePasswordCredentials(username, password)
        );

        // 创建低级 RestClient
        return RestClient.builder(new HttpHost(host, port))
                .setHttpClientConfigCallback(httpClientBuilder ->
                        httpClientBuilder.setDefaultCredentialsProvider(credentialsProvider))
                .build();
    }

    @Bean
    public ElasticsearchTransport elasticsearchTransport(RestClient restClient, ObjectMapper objectMapper) {
        // 配置 ObjectMapper 以正确序列化日期格式
        ObjectMapper esObjectMapper = objectMapper.copy();
        JavaTimeModule javaTimeModule = new JavaTimeModule();
        javaTimeModule.addSerializer(java.time.LocalDateTime.class, 
                new LocalDateTimeSerializer(java.time.format.DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
        esObjectMapper.registerModule(javaTimeModule);
        esObjectMapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);
        
        // 使用配置后的 ObjectMapper
        return new RestClientTransport(restClient, new JacksonJsonpMapper(esObjectMapper));
    }

    @Bean
    public ElasticsearchClient elasticsearchClient(ElasticsearchTransport transport) {
        // 创建 API 客户端
        return new ElasticsearchClient(transport);
    }
//
//    @Bean
//    @Primary
//    public VectorStore elasticsearchVectorStore(ElasticsearchClient elasticsearchClient, RestClient restClient, EmbeddingModel dashEmbeddingModel) {
//        String indexName = "partner-doc-ai-index";
//
//        // 在创建 VectorStore 之前，先删除旧索引（如果存在）
//        // 这样可以避免映射格式不兼容的问题
//        try {
//            boolean exists = elasticsearchClient.indices().exists(e -> e.index(indexName)).value();
//            if (exists) {
//                log.info("删除已存在的索引: {}", indexName);
//                elasticsearchClient.indices().delete(d -> d.index(indexName));
//                log.info("索引 {} 已删除，将重新创建", indexName);
//            }
//        } catch (Exception e) {
//            log.warn("检查或删除索引时出错: {}", e.getMessage());
//            // 如果删除失败，继续尝试创建，让 ElasticsearchVectorStore 处理
//        }
//
////        ElasticsearchVectorStoreOptions options = new ElasticsearchVectorStoreOptions();
////        options.setIndexName(indexName);
////        options.setDimensions(768);
////        // 暂时注释掉 similarity 配置，因为 Spring AI 1.0.0-M6 与 Elasticsearch 8.15.0 的兼容性问题
////        // 如果后续版本修复了这个问题，可以取消注释
////        // options.setSimilarity(SimilarityFunction.cosine);
////        return ElasticsearchVectorStore.builder(restClient, dashEmbeddingModel)
////                .options(options)
////                .initializeSchema(true)
////                .build();
//    }
}